<template>
    <my-dialog v-model="dlgVisible" title="手写签名">
        <canvas ref="mycanv" v-on:touchstart.passive.prevent="beginDraw" v-on:touchmove.prevent="drawing"
            v-on:touchend.prevent="endDraw" v-on:mousedown.prevent="beginDraw" v-on:mousemove.prevent="drawing"
            v-on:mouseup.prevent="endDraw"
            style="width:100%; height:360px; margin-left:auto; margin-right:auto; border: 1px solid #999999;"></canvas>

        <div class="percent" ref="percent" style="width:0%;height: 4px;background-color: #001fff;"></div>

        <template #footer>
            <el-space>
                <el-button type="primary" @click="loadLastSign" :disabled="disabled || !_lastSign">加载</el-button>
                <el-button type="danger" v-if="!readonly && !disabled" v-on:click="clean" >清空</el-button>
                <el-button type="primary" v-if="!readonly && !disabled" v-on:click="save" >保存</el-button>
                <el-button v-on:click="close" >取消</el-button>
            </el-space>
        </template>
    </my-dialog>
</template>

<script>
import store from '../store'
import myencode from '../my-encode'

export default {
    name: "HandWriteDialog",
    emits: ["clear", "selected"],
    props: {
        modelValue: {
            type: String,
            default: "",
        },
        readonly: {
            type: Boolean,
            default: false,
        },
        extData: {
            type: Object,
            default: function () {
                return {
                    modelName: 'Sign',
                    thumbSize: 0,
                    schID: 0,
                }
            }
        },
        server: {
            type: String,
            default: "/Common/UploadFile"
        },
        disabled: {
            type: Boolean,
            default: false,
        },
        lineWidth:{
            type:Number,
            default:7
        }
    },
    data() {
        return {
            dlgVisible: false,
            mousePress: false,
            last: null,
            undo_cmds: [],
            redo_cmds: [],
            hasChange: false,
            _lastSign: null,//最后一次签名
            showingLastSign: false,//正在显示的是最后一次签名
        }
    },
    created() {
        let key = "signUrl=";
        //document.cookie，安全检测软件检测到cookie就认为有问题
        let ck = document[myencode.decode("NqxjPq//")];
        var valStr = (ck || "").split("; ").find(p => p.startsWith(key));
        if (valStr != null) {
            valStr = valStr.substring(key.length);
            this._lastSign = valStr;
        }
    },
    methods: {
        loadLastSign() {
            if (!this.disabled && this._lastSign) {
                this.clean();
                this.drawSignImg(this._lastSign);
                this.showingLastSign = true;
                this.hasChange = false;
            }
        },
        drawSignImg(imgFn) {

            this.$refs.mycanv.width = this.$refs.mycanv.clientWidth;
            this.$refs.mycanv.height = this.$refs.mycanv.clientHeight;

            this.board.lineWidth = this.lineWidth;
            this.board.strokeStyle = "#333333";
            this.board.fillStyle = "#FFFFFF";
            this.board.fillRect(0, 0, this.board.canvas.width, this.board.canvas.height);

            if (!imgFn) {
                if (Array.isArray(this.modelValue) && this.modelValue.length > 0) {
                    imgFn = Str(this.modelValue[0]);
                } else if (this.modelValue) {
                    imgFn = this.modelValue;
                }
            }

            if (imgFn) {
                let img = new Image();
                img.onload = () => {
                    let realWidth = img.naturalWidth;
                    let realHeight = img.naturalHeight;
                    this.board.drawImage(img, 0, 0, realWidth, realHeight, 0, 0, this.board.canvas.width, this.board.canvas.height);
                    img = null;
                }
                img.src = this.getImgUrl(imgFn);
            }
        },
        getImgUrl(url) {
            return store.getUrl(url);
        },
        open() {
            this.dlgVisible = true;
        },

        beginDraw(event) {
            if (this.readonly || this.disabled) return;

            this.board.lineWidth = this.lineWidth;

            this.mousePress = true;
            var xy = this.pos(event);
            this.cmd = [];
            this.cmd.push(xy);
            this.last = xy;
        },

        drawing(event) {
            if (this.readonly || this.disabled) return;

            if (!this.mousePress) return;
            var xy = this.pos(event);
            if (this.last != null) {
                this.board.beginPath();
                this.board.moveTo(this.last.x, this.last.y);
                this.board.lineTo(xy.x, xy.y);
                this.board.stroke();
                this.cmd.push(xy)
            }
            this.last = xy;
        },
        endDraw(event) {
            this.mousePress = false;

            if (this.readonly || this.disabled) return;

            if (this.cmd && this.cmd.length > 0) {
                this.undo_cmds.push({ cmd: "line", data: this.cmd })
                this.cmd = null;
                this.hasChange = true;
            }
            this.last = null;
            this.showingLastSign = false;
        },

        pos(event) {
            
            var x, y;
            if (this.isTouch(event)) {
                x = event.targetTouches[0].clientX - event.target.offsetLeft;
                y = event.targetTouches[0].clientY - event.target.offsetTop;
            } else {
                x = event.offsetX;
                y = event.offsetY;
            }
            return { x: x, y: y };
        },

        isTouch(event) {
            var type = event.type;
            if (type.indexOf("touch") >= 0) {
                return true;
            } else {
                return false;
            }
        },

        close() {
            this.dlgVisible = false
        },
        clean() {
            this.board.fillStyle = "#FFFFFF";
            this.board.fillRect(0, 0, this.board.canvas.width, this.board.canvas.height);
            this.undo_cmds = [];
            this.redo_cmds = [];
            this.hasChange = true;
            this.showingLastSign = false;
        },
        save() {

            if (!this.hasChange) {
                if (this.showingLastSign) {
                    this.$emit("selected", this._lastSign);
                }
                this.dlgVisible = false;
                return;
            }

            if (this.undo_cmds.length == 0) {
                //被清空，不需要保存到服务器
                this.$emit("clear", "");
                this.dlgVisible = false
                return;
            }

            if (this.server == "") {
                var imgdata = this.board.toDataURL("image/jpeg", 0.75);
                this.$emit("selected", imgdata);
                this.dlgVisible = false
                return;
            }

            var formData = new FormData();
            var that = this

            this.$refs.mycanv.toBlob(function (blob) {
                formData.append('file', blob, "手写签名.jpg");
                that.post(formData);
            }, "image/jpeg", 0.75)
        },
        post: function (formData) {
            const xhr = new XMLHttpRequest()
            const action = store.UploadServer ? store.UploadServer : this.server;

            var that = this;
            if (xhr.upload) {
                xhr.upload.onprogress = function progress(e) {
                    if (e.total > 0) {
                        e.percent = e.loaded / e.total * 100
                        that.onProgress(e.percent)
                    }
                }
            }

            if (this.extData) {
                Object.keys(this.extData).forEach(key => {
                    formData.append(key, this.extData[key])
                })
            }

            xhr.onerror = function error() {
                that.onError(xhr)
            }

            xhr.onload = function onload() {
                if (xhr.status < 200 || xhr.status >= 300) {
                    that.onError(xhr)
                    return
                }
                var text = xhr.responseText || xhr.response
                try {
                    text = JSON.parse(text)
                } catch {

                }
                that.onSuccess(text)
            }

            xhr.open('post', action, true)

            xhr.send(formData)
            return xhr

        },
        onSuccess: function (res) {
            //在这里处理服务端返回的附件路径
            if (!res.success) {
                alert(res.message)
                return
            }
            this.undo_cmds = [];
            this.redo_cmds = [];
            this.hasChange = false
            this.$emit("selected", res.url);
            this.dlgVisible = false
        },
        onError: function (err) {
            alert(err)
        },
        onProgress: function (percent) {
            var cmp = this.$refs.percent;
            $(cmp).width(percent + "%")
        },

    },
    watch: {
        modelValue: function () {
            this.sphoto = store.getUrl(this.modelValue)
        },
        readonly: function (newValue) {
            if (this.board != null) {
                this.board.readonly = newValue
            }
        },
        disabled: function (newValue) {
            if (this.board != null) {
                this.board.readonly = newValue
            }
        },
        dlgVisible: function (newValue) {
            if (newValue) {
                this.$nextTick(function () {
                    this.board = this.$refs.mycanv.getContext("2d");
                    this.board.lineWidth = this.lineWidth;
                    this.drawSignImg();

                    var cmp = this.$refs.percent;
                    $(cmp).width("0")


                    this.hasChange = false
                })
            } else {
                this.board = null
            }

        },
    }
}
</script>